//----------------------------------------------------------------------------
//  ,-.
// /_\___ ,   Ninja Framework
// '  ___\    (C) Riccardo Capra - http://riccar.do
//  //   \\
//----------------------------------------------------------------------------
//  This program is free software: you can redistribute it and/or modify
//  it under the terms of the GNU General Public License as published by
//  the Free Software Foundation, either version 3 of the License, or
//  (at your option) any later version.
//
//  This program is distributed in the hope that it will be useful,
//  but WITHOUT ANY WARRANTY; without even the implied warranty of
//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
//  GNU General Public License for more details.
//
//  You should have received a copy of the GNU General Public License
//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
//----------------------------------------------------------------------------

#ifndef NJ_HIGH_RESOLUTION_TIMER_INLINE_H
#	define NJ_HIGH_RESOLUTION_TIMER_INLINE_H

	//----------------------------------------------------------------------------
	inline NjHighResolutionTimer::NjHighResolutionTimer()
	:
		m_uTime(0)
	{
	}
	//----------------------------------------------------------------------------
	inline NjHighResolutionTimer::NjHighResolutionTimer(NjHighResolutionTimer const & kCopy)
	:
		m_uTime(kCopy.m_uTime)
	{
	}
	//----------------------------------------------------------------------------
	inline NjHighResolutionTimer & NjHighResolutionTimer::operator=(NjHighResolutionTimer const & kCopy)
	{
		m_uTime=kCopy.m_uTime;
		return (*this);
	}
	//----------------------------------------------------------------------------
	inline NjHighResolutionTimer::operator NjBool() const
	{
		return !operator!();
	}
	//----------------------------------------------------------------------------
	inline NjBool NjHighResolutionTimer::operator!() const
	{
		return operator==(NjHighResolutionTimer());
	}
	//----------------------------------------------------------------------------
	inline NjBool NjHighResolutionTimer::operator==(NjHighResolutionTimer const & kRightValue) const
	{
		return m_uTime==kRightValue.m_uTime;
	}
	//----------------------------------------------------------------------------
	inline NjBool NjHighResolutionTimer::operator!=(NjHighResolutionTimer const & kRightValue) const
	{
		return !operator==(kRightValue);
	}
	//----------------------------------------------------------------------------
	inline void NjHighResolutionTimer::Start()
	{
		if ((m_uTime&FLAG_RUNNING)!=0)
			return;

		m_uTime-=GetTick();
		m_uTime|=FLAG_RUNNING;
	}
	//----------------------------------------------------------------------------
	inline void NjHighResolutionTimer::Pause()
	{
		if ((m_uTime&FLAG_RUNNING)==0)
			return;

		m_uTime+=GetTick();
		m_uTime&=(~FLAG_RUNNING);
	}
	//----------------------------------------------------------------------------
	inline void NjHighResolutionTimer::Reset()
	{
		if ((m_uTime&FLAG_RUNNING)!=0)
		{
			m_uTime=0-GetTick();
			NJ_ASSERT((m_uTime&FLAG_RUNNING)!=0);
		}
		else
			m_uTime=0;
	}
	//----------------------------------------------------------------------------
	inline NjHighResolutionTimer::TimeTick NjHighResolutionTimer::GetTickFrequency()
	{
		Initialize();
		return ms_uTickFrequency;
	}
	//----------------------------------------------------------------------------
	inline NjHighResolutionTimer::TimeTick NjHighResolutionTimer::GetTimeTick()
	{
		if (m_uTime&FLAG_RUNNING)
			return (m_uTime+GetTick())&(~FLAG_RUNNING);
		else
			return m_uTime;
	}
	//----------------------------------------------------------------------------
	inline NjFloat NjHighResolutionTimer::GetTimeS()
	{
		Initialize();
		return GetTimeTick()*ms_fTickPeriod;
	}
	//----------------------------------------------------------------------------

#endif // NJ_HIGH_RESOLUTION_TIMER_INLINE_H
